package com.huantai.common.util;

import java.math.BigDecimal;
import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.List;
import java.util.Locale;
import java.util.regex.Pattern;

import com.huantai.common.consts.RegularConst;
import com.huantai.common.exception.SystemException;

/**
 * 类型转换工具类
 * 
 * @author Ma Chao
 * @version 2018年4月17日 下午5:48:03
 */
public final class ConvertUtil {
    /** 不允许使用对象来调用工具类的方法 */
    private ConvertUtil() {}

    /**
     * String 转 int
     * 
     * @param str
     * @return int
     */
    public static int toInt(String str) {
        if (StringUtil.isEmpty(str)) {
            return 0;
        }
        int result = 0;
        try {
            result = Integer.parseInt(str);
        } catch (Exception e) {
            result = 0;
        }
        return result;
    }

    /**
     * String 转 long
     * 
     * @param str String
     * @return long
     */
    public static long toLong(String str) {
        if (StringUtil.isEmpty(str)) {
            return 0L;
        }

        long result = 0L;
        try {
            result = Long.parseLong(str);
        } catch (Exception e) {
            result = 0L;
        }
        return result;
    }

    /**
     * 安全的将小于Integer.MAX的long转为int，否则抛出IllegalArgumentException异常
     * 
     * @param l
     * @return int
     */
    public static int toInt32(long l) {
        if ((int) l == l) {
            return (int) l;
        }
        throw new SystemException("Int " + l + " out of range");
    }

    /**
     * String 转 float
     * 
     * @param str String
     * @return float
     */
    public static float toFloat(String str) {
        if (StringUtil.isEmpty(str)) {
            return 0f;
        }
        float result = 0f;
        try {
            result = Float.parseFloat(str);
        } catch (Exception e) {
            result = 0f;
        }
        return result;
    }

    /**
     * String 转 double
     * 
     * @param str String
     * @return double
     */
    public static double toDouble(String str) {
        if (StringUtil.isEmpty(str)) {
            return 0f;
        }
        double result = 0f;
        try {
            result = Double.parseDouble(str);
        } catch (Exception e) {
            result = 0f;
        }
        return result;
    }

    /**
     * int 转 String
     * 
     * @param v int
     * @return String
     */
    public static String toString(int v) {
        return Integer.toString(v);
    }

    /**
     * long 转 String
     * 
     * @param v long
     * @return String
     */
    public static String toString(long v) {
        return Long.toString(v);
    }

    /**
     * float 转 String，四舍五入保留2位小数
     * 
     * @param v float
     * @return String
     */
    public static String toString(float v) {
        BigDecimal value = BigDecimal.valueOf(v);
        return BigDecimalUtil.round(value, 2).toString();
    }

    /**
     * double 转 String，四舍五入保留2位小数
     * 
     * @param v double
     * @return String
     */
    public static String toString(double v) {
        BigDecimal value = BigDecimal.valueOf(v);
        return BigDecimalUtil.round(value, 2).toString();
    }

    /**
     * 输出格式化为小数后两位的double字符串
     * 
     * @param v double
     * @return String
     */
    public static String to2DigitString(double v) {
        return String.format(Locale.ROOT, "%.2f", v);
    }

    /**
     * 按百分比展示
     * 
     * @param v value
     * @return String
     */
    public static String toPercentString(BigDecimal v) {
        DecimalFormat decimalFormat = new DecimalFormat("0.00%");
        return decimalFormat.format(v);
    }

    /**
     * 将百分比表示的字符串转成数值型，保留6位小数
     * 
     * @param percentStr 百分比字符串，例如 "1.68%" =>> 0.016800，"1.68" =>> 0.016800
     * @return 实际数值
     */
    public static BigDecimal parsePercentString(String percentStr) {
        percentStr = percentStr.replace("%", "");
        return new BigDecimal(percentStr).divide(BigDecimal.valueOf(100), 6,
                BigDecimal.ROUND_HALF_UP);
    }

    /**
     * 金额单位从元转成分
     * 
     * @param yuan 金额，单位元 ，例如 12.35元 =>> 1235分
     * @return 金额，单位分
     */
    public static BigDecimal yuan2Fen(BigDecimal yuan) {
        return BigDecimalUtil.multiply(yuan, BigDecimal.valueOf(100.00), 0);
    }

    /**
     * 金额单位从分转成元
     * 
     * @param fen 金额，单位分 ，例如 1235分 =>> 12.35元
     * @return 金额，单位元
     */
    public static BigDecimal fen2Yuan(BigDecimal fen) {
        return BigDecimalUtil.divide(fen, BigDecimal.valueOf(100), 2);
    }

    /**
     * 将字符串类型的数字分割成单个数字的数组
     * 
     * @param numberStr 要分割的字符串
     * @return 单个数字的数组
     */
    public static List<String> splitNumber(String numberStr) {
        if (StringUtil.isEmpty(numberStr)) {
            return new ArrayList<>();
        }
        // 最多2位小数的数字字符串
        if (!Pattern.matches(RegularConst.AmountOfMoney.EXPRESSION, numberStr)) {
            return new ArrayList<>();
        }

        List<String> list = new ArrayList<>();
        int size = numberStr.length();
        for (int i = 0; i < size; i++) {
            list.add(String.valueOf(numberStr.charAt(i)));
        }
        return list;
    }
}
